package groups.common.dao;

import groups.common.DBDumper;
import groups.common.User;

import java.io.IOException;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.sql.Connection;
import java.sql.SQLException;
import java.sql.Statement;
import java.util.Vector;



public class SQLTableBak{

	private String tableName;
	private Connection connection;
	private Class<?> tableClass;
	private Vector<ColumnMethod> methods;
	private String insertStatement;
	
	public SQLTableBak(Class<?> tableClass,String tableName, Connection connection){
		this.tableName = tableName;
		this.connection = connection;
		this.tableClass = tableClass;
		methods = new Vector<SQLTableBak.ColumnMethod>();
	}
	
	public void addColumnMethod(String columnName, String methodName, boolean auto_increment)
			throws SecurityException, NoSuchMethodException{
		
		Method m = tableClass.getMethod(methodName);
		methods.add(new ColumnMethod(m, columnName, auto_increment));
		
		updateInsertStatement();
	}
	
	public void insert(Object obj) 
			throws IllegalArgumentException, IllegalAccessException, InvocationTargetException, SQLException{
		String query = createInsertQuery(obj);
		
		Statement stm = connection.createStatement();
		System.out.println(query);
		stm.executeUpdate(query);
	}
	
	public void deleteAny(Object obj){
		
	}
	
	public void deleteExact(Object obj){
		
	}
	
	
	private void updateInsertStatement(){
		StringBuilder columns=new StringBuilder("(");
		for (ColumnMethod cm : methods) {
			if(cm.isAutoIncrement()==false)
				columns.append(cm.getTableColumn()+',');
		}
		
		columns.deleteCharAt(columns.length()-1);
		columns.append(")");
		
		insertStatement = String.format("insert into %s %s values(%%s)", tableName,columns.toString());
		
	}
	
	private String createInsertQuery(Object obj)
			throws IllegalArgumentException, IllegalAccessException, InvocationTargetException{
		
		String res="";
		
		for (ColumnMethod method : methods) {
			if(method.isAutoIncrement()==false){
				if (method.getMethod().invoke(obj).getClass().getName().equals("java.lang.String"))
					res+= "'" + method.getMethod().invoke(obj).toString() + "',";
				else res+= method.getMethod().invoke(obj).toString() + ",";
			}
		}
		
		return String.format(insertStatement, res.substring(0, res.length()-1));
	}
	
	private void updateDeleteStatement(){
		
	}
	

	public static void main(String[] args){

		try {
			DBDumper dumper = new DBDumper("org.apache.derby.jdbc.EmbeddedDriver", "jdbc:derby:endemics;create=true", "", "");
			Connection con = dumper.initDB();
			SQLTableBak table = new SQLTableBak(User.class, "\"USER\"", con);
			
			table.addColumnMethod("idUser", "getIdUser", true);
			table.addColumnMethod("name", "getName", false);
			table.addColumnMethod("passkey", "getPasskey" , false);
			table.addColumnMethod("type", "getType", false);
			User user = new User();
			user.setIdUser(1);
			user.setName("Teste");
			user.setPasskey("1234");
			user.setType(2);
			
			table.insert(user);
			
			
			
		} catch (SecurityException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		} catch (NoSuchMethodException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		} catch (IllegalArgumentException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		} catch (IllegalAccessException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		} catch (InvocationTargetException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		} catch (SQLException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		} catch (ClassNotFoundException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		} catch (IOException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
		
		
	}
	/*
	 * Classe auxiliar da SQLTable
	 */
	
	private static class ColumnMethod{
		private Method method;
		private boolean autoIncrement;
		private String tableColumn;
		
		public ColumnMethod(Method method,String tableColumn, boolean autoIncrement) {
			this.method = method;
			this.autoIncrement = autoIncrement;
			this.tableColumn = tableColumn;
		}

		public Method getMethod() {
			return method;
		}

		public boolean isAutoIncrement() {
			return autoIncrement;
		}

		public String getTableColumn() {
			return tableColumn;
		}

	}

}
